home *** CD-ROM | disk | FTP | other *** search
- #define APPLE_EVENT_C
- #include "AppleEvent.h"
-
-
- #if defined(__MWERKS__)
- #pragma segment __%Main
- #else
- #pragma segment Main
- #endif
-
-
- struct triplets
- {
- AEEventClass theEventClass;
- AEEventID theEventID;
- ProcPtr theHandler;
- AEEventHandlerUPP theUPP;
- };
- typedef struct triplets triplets;
-
- static triplets keywordsToInstall[] =
- {
- // These are the four required AppleEvents.
-
- { kCoreEventClass, kAEOpenApplication, (ProcPtr) DoAEOpenApplication },
- { kCoreEventClass, kAEOpenDocuments, (ProcPtr) DoAEOpenDocuments },
- { kCoreEventClass, kAEPrintDocuments, (ProcPtr) DoAEPrintDocuments },
- { kCoreEventClass, kAEQuitApplication, (ProcPtr) DoAEQuitApplication },
-
- // These are the Abalone AppleEvents.
-
- { kAbaloneEventClass, kSendMove, (ProcPtr) DoAEMove },
- { kAbaloneEventClass, kSendGame, (ProcPtr) DoAEGame },
- { kAbaloneEventClass, kSendInit, (ProcPtr) DoAEInit },
- { kAbaloneEventClass, kSendNew1, (ProcPtr) DoAENew1 },
- { kAbaloneEventClass, kSendAdrs, (ProcPtr) DoAEAdrs },
- { kAbaloneEventClass, kSendStop, (ProcPtr) DoAEStop }
- };
-
-
-
- Boolean gHasPPCToolbox = true; // Test for system 7 done elsewhere
-
-
-
-
- // Intializes our AppleEvent dispatcher table.
-
- void
- InitAppleEvents (void)
- {
- OSErr err;
- short i;
-
- for (i = 0; i < (sizeof(keywordsToInstall) / sizeof(triplets)); ++i)
- {
- if (!keywordsToInstall[i].theUPP)
- keywordsToInstall[i].theUPP = NewAEEventHandlerProc(keywordsToInstall[i].theHandler);
-
- err = AEInstallEventHandler(
- keywordsToInstall[i].theEventClass, // What class to install.
- keywordsToInstall[i].theEventID, // Keywords to install.
- keywordsToInstall[i].theUPP, // The AppleEvent handler.
- 0L, // Unused refcon.
- false // Only for our app.
- );
-
- Assert (err == noErr, HIGH_LEVEL_EVENT_INSTALL);
- }
- }
-
-
-
- void
- DoHighLevelEvent (EventRecord *event)
- {
- if (AEProcessAppleEvent (event) != noErr)
- // Warning (HIGH_LEVEL_EVENT_FAIL);
- ;
- }
-
-
-
- OSErr
- GetTargetInfo ( AEAddressDesc targetDesc,
- char *zone,
- char *machine,
- char *application
- )
- {
- ProcessSerialNumber targetPSN;
- PortInfoRec portInfo;
- TargetID theTargetID;
- OSErr err = noErr;
-
- zone[0] = 0;
- machine[0] = 0;
- application[0] = 0;
-
- if (targetDesc.descriptorType == typeProcessSerialNumber)
- {
- targetPSN = **(ProcessSerialNumber **)(targetDesc.dataHandle);
- err = GetPortNameFromProcessSerialNumber (&portInfo.name, &targetPSN);
- if (!err) pstrcpy (application, (char *) portInfo.name.name);
- return err;
- }
- if (targetDesc.descriptorType == typeTargetID)
- {
- theTargetID = **(TargetID **)(targetDesc.dataHandle);
- switch (theTargetID.location.locationKindSelector)
- {
- case ppcNoLocation:
- break;
- case ppcNBPLocation:
- pstrcpy(zone, (char *) theTargetID.location.u.nbpEntity.zoneStr);
- pstrcpy(machine, (char *) theTargetID.location.u.nbpEntity.objStr);
- break;
- case ppcNBPTypeLocation:
- break;
- }
- pstrcpy (application, (char *) theTargetID.name.name);
- return noErr;
- }
-
- return errAEWrongDataType;
- }
-
-
-
-
-
- /* MakeTarget
- **
- ** Creates a TargetID.
- **
- ** If sendDirect is TRUE, the target is specified by setting a
- ** ProcessSerialNumber to kCurrentProcess. This has the advantage of sending
- ** the message directly to ourselves, bypassing ePPC and gaining about a 10-15x
- ** speed improvement. If sendDirect is FALSE, we see if we have the
- ** PPCToolBox. If not, then we are forced to do a direct send. If we do have
- ** the PPCToolbox, then we call PPCBrowser. We then look at the reply, and
- ** factor in the mode we are going to use in AESend. If that mode is
- ** kAEWaitReply and the user selected us as the target, we have to turn that
- ** into a direct send. This is because the AppleEvent Manager will otherwise
- ** post the event as a high-level event. However, we are busy waiting for a
- ** reply, not looking for events, so we'll hang. We avoid this by forcing a
- ** direct send.
- */
-
- OSErr
- MakeTarget ( AEAddressDesc *target,
- Boolean sendDirect,
- short replyMode,
- Str255 prompt,
- Str255 applListLabel,
- PPCFilterUPP portFilter
- )
- {
- OSErr err;
- ProcessSerialNumber targetPSN;
- ProcessSerialNumber myPSN;
- TargetID theTargetID;
- Boolean sendingToSelf;
-
- static LocationNameRec location;
- static PortInfoRec portInfo;
- static Boolean defaultOK = false;
-
- err = noErr; /* Make sure we do the code for the second main if. */
-
- target->dataHandle = nil;
- /* Assume we will fail and nil this descriptor out. */
-
- if (!sendDirect) {
- if (!gHasPPCToolbox)
- sendDirect = true; /* No tools to send with, so send direct. */
-
- else { /* We are not sending to self. */
- /* sendDirect is false. */
- err = PPCBrowser(
- prompt, /* Browse dialog box prompt. */
- applListLabel, /* The 'programs' list title. */
- defaultOK, /* Initially false. */
- &location, /* Correct if defaultOK is true. */
- &portInfo, /* Correct if defaultOK is true. */
- portFilter, /* No port filtering. */
- nil /* List ports of type 'PPCToolBox'. */
- );
-
- if (!err) { /* If user didn't cancel... */
- defaultOK = true; /* Default to the same port next time. */
- if (replyMode == kAEWaitReply) {
- /* Sender wants a reply and will be waiting... */
-
- sendingToSelf = false;
- /* Assume that we aren't sending to ourselves. */
-
- if (!location.locationKindSelector) {
- /* Hey, we are sending to ourselves! */
-
- err = GetProcessSerialNumberFromPortName(
- &portInfo.name, &targetPSN);
- if (!err) {
- GetCurrentProcess(&myPSN);
- err = SameProcess(&targetPSN, &myPSN, &sendingToSelf);
- }
- }
-
- if (sendingToSelf) sendDirect = true;
-
- }
- }
- }
- }
-
- if (!err) {
- if (sendDirect) {
- /* Finally, we get to the point... */
-
- targetPSN.highLongOfPSN = 0;
- targetPSN.lowLongOfPSN = kCurrentProcess;
- /* Process serial # is equal to kCurrentProcess. This
- ** bypasses ePPC and speeds up things considerably. */
-
- err = AECreateDesc(
- typeProcessSerialNumber, /* Standard PSN descriptor type. */
- (Ptr)&targetPSN, /* "No ePPC" process serial #. */
- sizeof(targetPSN), /* Size of data (2 longs). */
- target /* Wherefore art thou desc. */
- );
- }
- else {
- theTargetID.location = location;
- theTargetID.name = portInfo.name;
- /* The fields sessionID does not need to be filled in now.
- ** The sessionID is returned when you actually connect to
- ** a port. You can then use the sessionID from that point
- ** on to improve speed.
- **
- ** You also don't need to fill in the recvrName field at this
- ** point. This is filled in, again, when the session is
- ** actually established.
- **
- ** The amount of data for a non-us target is bigger.
- ** We need the whole dealie for our target, since
- ** it is out on the net somewhere. */
-
- err = AECreateDesc(
- typeTargetID, /* Standard target descriptor type. */
- (Ptr)&theTargetID, /* The data for the descriptor. */
- sizeof(theTargetID), /* Size of the data. */
- target /* Wherefore art thou desc. */
- );
- }
- }
- return (err);
- }
-